/*
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2, or (at your option)
 * any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
 * 02111-1307, USA.
 *
 * http://www.gnu.org/copyleft/gpl.html
 */
package com.Server;

/**
 * <p>
 * 最低値lowと最大値highによって囲まれた、数値の範囲を指定するクラス。
 * </p>
 * <p>
 * <b>このクラスは同期化されない。</b> 複数のスレッドが同時にこのクラスのインスタンスにアクセスし、
 * 1つ以上のスレッドが範囲を変更する場合、外部的な同期化が必要である。
 * </p>
 */
public class IntRange {
	
	public static int ensure(final int n, final int low, final int high) {
		int r = n;
		r = low <= r ? r : low;
		r = r <= high ? r : high;
		return r;
	}
	public static boolean includes(final int i, final int low, final int high) {
		return low <= i && i <= high;
	}

	private final int _low;

	private final int _high;

	public IntRange(final int low, final int high) {
		this._low = low;
		this._high = high;
	}

	public IntRange(final IntRange range) {
		this(range._low, range._high);
	}

	/**
	 * 数値iを、この範囲内に丸める。
	 * 
	 * @param i
	 *            数値
	 * @return 丸められた値
	 */
	public int ensure(final int i) {
		int r = i;
		r = this._low <= r ? r : this._low;
		r = r <= this._high ? r : this._high;
		return r;
	}

	@Override
	public boolean equals(final Object obj) {
		if (!(obj instanceof IntRange)) {
			return false;
		}
		final IntRange range = (IntRange) obj;
		return this._low == range._low && this._high == range._high;
	}

	public int getHigh() {
		return this._high;
	}

	public int getLow() {
		return this._low;
	}

	public int getWidth() {
		return this._high - this._low;
	}

	/**
	 * 数値iが、範囲内にあるかを返す。
	 * 
	 * @param i
	 *            数値
	 * @return 範囲内であればtrue
	 */
	public boolean includes(final int i) {
		return this._low <= i && i <= this._high;
	}

	/**
	 * この範囲内からランダムな値を生成する。
	 * 
	 * @return 範囲内のランダムな値
	 */
	public int randomValue() {
		return Random.nextInt(this.getWidth() + 1) + this._low;
	}

	@Override
	public String toString() {
		return "low=" + this._low + ", high=" + this._high;
	}
}
